﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Windows.Media.Imaging;
using Autodesk.Internal.Windows;
using Autodesk.Revit.Attributes;
using Autodesk.Revit.UI;
using Autodesk.Revit.UI.Events;
using Autodesk.Windows;
using YArchitech.LIB;
using YArchitech.Public.Encrypt;

namespace YArchitech.Public
{
	[Transaction(TransactionMode.Manual)]
	[Journaling(JournalingMode.NoCommandData)]
	[Regeneration(RegenerationOption.Manual)]
	public class Application : IExternalApplication
	{
		private static string GetUserSetting(string section, string key, string def = "")
		{
			string configFile = Product.ConfigFile;
			return IniHelper.GetSetting(section, key, configFile, def);
		}

		private static string GetDefaultSetting(string section, string key, string def = "")
		{
			string defaultConfigFile = Product.DefaultConfigFile;
			return IniHelper.GetSetting(section, key, defaultConfigFile, def);
		}

		public static int GetDisciplineType()
		{
			string userSetting = Application.GetUserSetting("Product", "DisciplineType", "2");
			int num = 2;
			int.TryParse(userSetting, out num);
			if (num < 0 || num > 31)
			{
				num = 2;
			}
			return num;
		}

		public static bool HasDiscipline(int type, int dt)
		{
			int num = dt - 1;
			return num >= 0 && 1 == (type >> num & 1);
		}

		private string[] GetRibbonFiles(string disciplineCode)
		{
			string[] result;
			try
			{
				string text = ",";
				string text2 = Application.GetDefaultSetting("Ribbon", disciplineCode, "").Trim();
				string[] array = text2.Split(text.ToCharArray());
				result = array;
			}
			catch
			{
				result = null;
			}
			return result;
		}

		private static void AddString(List<string> target, IEnumerable<string> sub)
		{
			if (sub == null || sub.Count<string>() == 0)
			{
				return;
			}
			foreach (string item in sub)
			{
				if (!target.Contains(item))
				{
					target.Add(item);
				}
			}
		}

		private IEnumerable<string> GetRibbonFiles()
		{
			int disciplineType = Application.GetDisciplineType();
			List<string> list = new List<string>();
			if (Product.IsArchitecture() || Product.IsFamliyLeader())
			{
				Application.AddString(list, this.GetRibbonFiles("Architecture"));
			}
			else if (Product.IsEDD())
			{
				Application.AddString(list, this.GetRibbonFiles("EDD"));
			}
            //else if (Product.IsMEI())
            //{
            //    Application.AddString(list, this.GetRibbonFiles("MEI"));
            //}
			else
			{
				if (Application.HasDiscipline(disciplineType, 2))
				{
					Application.AddString(list, this.GetRibbonFiles("HVAC"));
				}
				if (Application.HasDiscipline(disciplineType, 3))
				{
					Application.AddString(list, this.GetRibbonFiles("Drainage"));
				}
				if (Application.HasDiscipline(disciplineType, 4))
				{
					Application.AddString(list, this.GetRibbonFiles("Electric"));
				}
			}
			int num = list.Count<string>();
			string[] array = new string[num];
			for (int i = 0; i < num; i++)
			{
				string text = list.ElementAt(i).Trim();
				if (!text.EndsWith(".xml", StringComparison.OrdinalIgnoreCase))
				{
					text += ".xml";
				}
				array[i] = Path.Combine(Product.DataLocation, text);
			}
			return array;
		}

		private bool DeleteAddinFile()
		{
			bool result;
			try
			{
				if (Product.BeJustStarting() || Product.BeStartingAtTheSameTime())
				{
					List<string> platformAllAddInFolders = Product.GetPlatformAllAddInFolders();
					if (platformAllAddInFolders == null || platformAllAddInFolders.Count < 1)
					{
						result = false;
					}
					else
					{
						foreach (string path in platformAllAddInFolders)
						{
							if (Product.IsArchitecture())
							{
								List<string> list = Product.GetHYRMESourceAddInFile().ToList<string>();
								list = this.GetNewNameList(list);
								if (list != null)
								{
									Product.GetOrDelAddinFile(path, list, true);
								}
							}
							else if (Product.IsRME())
							{
								List<string> list = Product.GetYJKArchSourceAddInFile().ToList<string>();
								list = this.GetNewNameList(list);
								if (list != null)
								{
									Product.GetOrDelAddinFile(path, list, true);
								}
							}
							if (Product.BeJustStarting())
							{
								List<string> list = Product.GetSourceAddInFile(true).ToList<string>();
								if (list != null)
								{
									Product.GetOrDelAddinFile(path, list, false);
								}
							}
							Product.CopySpecAddInFile();
						}
						result = true;
					}
				}
				else
				{
					string userSetting = Application.GetUserSetting("StartUp", "AddInFolder", "");
					string defaultSetting = Application.GetDefaultSetting("Addin", "SOURCE_FILENAME", "YArchitech.addin");
					if (string.IsNullOrEmpty(defaultSetting))
					{
						result = false;
					}
					else
					{
						char[] separator = new char[]
						{
							','
						};
						string[] array = defaultSetting.Split(separator, StringSplitOptions.RemoveEmptyEntries);
						if (array == null || array.Length == 0)
						{
							result = false;
						}
						else
						{
							foreach (string text in array)
							{
								string text2 = text.Trim();
								if (!text2.EndsWith(".addin", StringComparison.OrdinalIgnoreCase))
								{
									text2 += ".addin";
								}
								string path2 = Path.Combine(userSetting, text2.Insert(0, "00"));
								if (File.Exists(path2))
								{
									File.Delete(path2);
								}
							}
							result = true;
						}
					}
				}
			}
			catch (Exception ex)
			{
				ex.ToString();
				result = false;
			}
			return result;
		}

		private List<string> GetNewNameList(List<string> addInList)
		{
			if (addInList == null || addInList.Count < 1)
			{
				return addInList;
			}
			List<string> list = new List<string>();
			for (int i = 0; i < addInList.Count; i++)
			{
				list.Add(addInList[i].Insert(0, "00"));
			}
			return list;
		}

		public VerticalMenuCommandTableInfos GetHYMenuInfos()
		{
			IEnumerable<string> ribbonFiles = this.GetRibbonFiles();
			if (ribbonFiles == null || ribbonFiles.Count<string>() == 0)
			{
				return null;
			}
			Ribbon ribbon = new Ribbon();
			return ribbon.GetHYMenuInfos(ribbonFiles, Product.BinLocation, Product.ResLocation);
		}

		private static void InitEnvironment_Temp()
		{
			string baseDirectory = AppDomain.CurrentDomain.BaseDirectory;
			string[] array = new string[]
			{
				"apidsp_windows.dll",
				"apidsp_windows_x64.dll",
				"hasp_windows_100561.dll",
				"hasp_windows_x64_100561.dll"
			};
			try
			{
				foreach (string path in array)
				{
					string sourceFileName = Path.Combine(Product.BinLocation, path);
					string destFileName = Path.Combine(baseDirectory, path);
					File.Copy(sourceFileName, destFileName, false);
				}
			}
			catch
			{
			}
		}

		private static void InitEnvironment()
		{
			Application.origionPath = Environment.GetEnvironmentVariable("Path", EnvironmentVariableTarget.Process);
			string value = Product.BinLocation + ";";
			Environment.SetEnvironmentVariable("Path", value, EnvironmentVariableTarget.Process);
		}

		private static void ResetEnvironment()
		{
			Environment.SetEnvironmentVariable("Path", Application.origionPath, EnvironmentVariableTarget.Process);
		}

		public Result OnStartup(UIControlledApplication application)
		{
			ComponentManager.ItemExecuted += Application.OnItemExecuted;
			Application.InitEnvironment();
			CmdTools.RibbonEnabled = true;
			CmdTools.uiApp = application;
			Result result;
			try
			{
				application.Idling += this.OnIdling;
				Program.Init(null);
				if (!Program.LicenseValide)
				{
					Application.ResetEnvironment();
					result = Autodesk.Revit.UI.Result.Failed;
				}
				else
				{
					this.CreateHYRibbon(application);
					Process currentProcess = Process.GetCurrentProcess();
					IntPtr mainWindowHandle = currentProcess.MainWindowHandle;
					Program.OnUpdate(mainWindowHandle);
					result = Autodesk.Revit.UI.Result.Succeeded;
				}
			}
			catch (Exception ex)
			{
				string message = ex.Message;
                Autodesk.Revit.UI.TaskDialog.Show("盈建科提示", string.Concat(new string[]
				{
					"创建盈建科菜单失败！",
					Environment.NewLine,
					"如果是同一时间启动多个HYBIM类软件,请错开一点启动时间,等一个启动完成以后,再启动另一个。",
					Environment.NewLine,
					"如果不是以上原因，可能是菜单文件损坏，请重新安装盈建科软件或与盈建科客服联系!"
				}));
				result = Autodesk.Revit.UI.Result.Failed;
			}
			finally
			{
				Application.ResetEnvironment();
				this.DeleteAddinFile();
			}
			return result;
		}

		public Result OnShutdown(UIControlledApplication application)
		{
			Application.ResetEnvironment();
			this.DeleteAddinFile();
			Program.Clear();
			return Autodesk.Revit.UI.Result.Succeeded;
		}

		private void OnLicenseError(object sender, EventArgs e)
		{
			CmdTools.RibbonEnabled = false;
            Autodesk.Revit.UI.TaskDialog.Show("盈建科提示", "获取许可证失败！");
			this.DisableRibbon();
		}

		private void OnIdling(object sender, IdlingEventArgs e)
		{
			bool ribbonEnabled = CmdTools.RibbonEnabled;
			if (!Program.LicenseValide && this.num == 0)
			{
				this.DisableRibbon();
				this.num++;
			}
		}

		private void DisableRibbon_OLD()
		{
			if (this.panels == null)
			{
				return;
			}
			try
			{
                foreach (Autodesk.Revit.UI.RibbonPanel ribbonPanel in this.panels)
				{
                    foreach (Autodesk.Revit.UI.RibbonItem ribbonItem in ribbonPanel.GetItems())
					{
						ribbonItem.Enabled = false;
					}
				}
			}
			catch
			{
			}
		}

		private void DisableRevitRibbon()
		{
			if (this.ribbonDisabled)
			{
				if (this.ActiveTab != null)
				{
					this.DisableRibbonTab(this.ActiveTab);
					this.ActiveTab = null;
				}
				return;
			}
			if (this.hyTabs == null)
			{
				return;
			}
			try
			{
				foreach (RibbonTab ribbonTab in this.hyTabs)
				{
					this.DisableRibbonTab(ribbonTab);
				}
				this.ribbonDisabled = true;
			}
			catch
			{
			}
		}

		private void DisableRibbon()
		{
			if (this.ribbonDisabled)
			{
				if (this.ActiveTab != null)
				{
					if (this.ActiveTab.IsActive)
					{
						return;
					}
					this.DisableRibbonTab(this.ActiveTab);
					this.ActiveTab = null;
				}
				return;
			}
			if (this.hyTabs == null)
			{
				return;
			}
			try
			{
                Autodesk.Revit.UI.TaskDialog.Show("盈建科提示", "获取许可证失败！");
				foreach (RibbonTab ribbonTab in this.hyTabs)
				{
					if (ribbonTab.IsActive)
					{
						this.ActiveTab = ribbonTab;
						AuthorizeLicenseChecker.CheckSecond = 10;
					}
					else
					{
						this.DisableRibbonTab(ribbonTab);
					}
				}
				this.ribbonDisabled = true;
			}
			catch
			{
			}
		}

        private void DisableRibbonTab(RibbonTab ribbonTab)
		{
            foreach (Autodesk.Windows.RibbonPanel ribbonPanel in ribbonTab.Panels)
			{
				ribbonPanel.IsEnabled = false;
			}
		}

		private void CreateHYRibbon(UIControlledApplication application)
		{
			IEnumerable<string> ribbonFiles = this.GetRibbonFiles();
			if (ribbonFiles == null || ribbonFiles.Count<string>() == 0)
			{
				return;
			}
			Ribbon ribbon = new Ribbon();
			this.panels = ribbon.CreateTabs(application, Product.BinLocation, ribbonFiles, Product.ResLocation);
			if (this.panels == null || CmdTools.listTabName == null || CmdTools.listTabName.Count<string>() == 0 || ComponentManager.Ribbon == null || ComponentManager.Ribbon.Tabs == null || ComponentManager.Ribbon.Tabs.Count == 0)
			{
				return;
			}
			this.hyTabs = new List<RibbonTab>();
			using (List<string>.Enumerator enumerator = CmdTools.listTabName.GetEnumerator())
			{
				while (enumerator.MoveNext())
				{
					string hyTabName = enumerator.Current;
					RibbonTab ribbonTab = ComponentManager.Ribbon.Tabs.First((RibbonTab T) => T.Title == hyTabName);
					if (ribbonTab != null)
					{
						this.hyTabs.Add(ribbonTab);
						ComponentManager.Ribbon.Tabs.Remove(ribbonTab);
					}
				}
			}
			int num = 0;
			foreach (RibbonTab ribbonTab2 in this.hyTabs)
			{
				ComponentManager.Ribbon.Tabs.Insert(num++, ribbonTab2);
                if (ribbonTab2.Panels != null && ribbonTab2.Panels.Count<Autodesk.Windows.RibbonPanel>() != 0)
				{
                    foreach (Autodesk.Windows.RibbonPanel ribbonPanel in ribbonTab2.Panels)
					{
						if (ribbonPanel.Source != null && ribbonPanel.Source.Items != null)
						{
                            foreach (Autodesk.Windows.RibbonItem ribbonItem in ribbonPanel.Source.Items)
							{
								this.AddToolTip(ribbonTab2.Title, ribbonPanel.Source.Title, ribbonItem);
							}
						}
					}
				}
			}
		}

        private void AddToolTip(string tabTitle, string panelTitle, Autodesk.Windows.RibbonItem ribbonItem)
		{
			if (ribbonItem is RibbonRowPanel)
			{
				RibbonRowPanel ribbonRowPanel = ribbonItem as RibbonRowPanel;
				if (ribbonRowPanel != null && ribbonRowPanel.Items != null)
				{
                    foreach (Autodesk.Windows.RibbonItem ribbonItem2 in ribbonRowPanel.Items)
					{
						this.AddToolTip(tabTitle, panelTitle, ribbonItem2);
					}
				}
				return;
			}
			if (!(ribbonItem is RibbonListButton))
			{
				this.SetItemTooltip(tabTitle, panelTitle, ribbonItem);
				return;
			}
			RibbonListButton ribbonListButton = ribbonItem as RibbonListButton;
			if (ribbonListButton.Items == null)
			{
				return;
			}
            foreach (Autodesk.Windows.RibbonItem ribbonItem3 in ribbonListButton.Items)
			{
				this.AddToolTip(tabTitle, panelTitle, ribbonItem3);
			}
		}

        private void SetItemTooltip(string tabTitle, string panelTitle, Autodesk.Windows.RibbonItem ribbonItem)
		{
			if (ribbonItem == null)
			{
				return;
			}
			string key = HYRibbonItemToolTipData.ConstructKey(tabTitle, panelTitle, ribbonItem.Text);
			HYRibbonItemToolTipData hyribbonItemToolTipData = null;
			if (!CmdTools.HYRibbonItems.TryGetValue(key, out hyribbonItemToolTipData))
			{
				return;
			}
			RibbonToolTip ribbonToolTip = new RibbonToolTip
			{
				Title = hyribbonItemToolTipData.ItemName,
				Content = hyribbonItemToolTipData.Content
			};
			if (!string.IsNullOrEmpty(hyribbonItemToolTipData.ExpandedContent))
			{
				ribbonToolTip.ExpandedContent = hyribbonItemToolTipData.ExpandedContent;
			}
			if (!string.IsNullOrEmpty(hyribbonItemToolTipData.ExpandedImage))
			{
				ribbonToolTip.ExpandedImage = new BitmapImage(new Uri(hyribbonItemToolTipData.ExpandedImage, UriKind.Absolute));
			}
			if (!string.IsNullOrEmpty(hyribbonItemToolTipData.ExpandedVideo))
			{
				ribbonToolTip.ExpandedVideo = new Uri(hyribbonItemToolTipData.ExpandedVideo, UriKind.Absolute);
			}
			ribbonItem.ToolTip = ribbonToolTip;
		}

		private void OnRibbonItemHostEvent(object sender, HostEventArgs e)
		{
            Autodesk.Revit.UI.TaskDialog.Show("OnRibbonItemHostEvent 1", "OnRibbonItemHostEvent 2");
			if (e.Target == RibbonHostEventTargets.Active)
			{
                Autodesk.Revit.UI.TaskDialog.Show("OnRibbonItemHostEvent", "OnRibbonItemHostEvent");
			}
		}

		private static void OnItemExecuted(object sender, RibbonItemExecutedEventArgs e)
		{
			Application.LogUserCommand(e.Item);
		}

        private static void LogUserCommand(Autodesk.Windows.RibbonItem ribbonItem)
		{
			try
			{
				string path = DateTime.Now.ToString("yyyyMM") + ".log";
				string path2 = Path.Combine(Application.CmdLogDirectory, path);
				Directory.CreateDirectory(Application.CmdLogDirectory);
				StreamWriter streamWriter = File.AppendText(path2);
				streamWriter.WriteLine("{0},{1},{2},{3}", new object[]
				{
					ribbonItem.Id,
					DateTime.Now.ToString("yyyyMMdd HH:mm:ss"),
					Environment.MachineName,
					Environment.UserName
				});
				streamWriter.Close();
			}
			catch (Exception)
			{
			}
		}

        private List<Autodesk.Revit.UI.RibbonPanel> panels;

		private List<RibbonTab> hyTabs;

		private static string origionPath = string.Empty;

		private int num;

		private bool ribbonDisabled;

		private RibbonTab ActiveTab;

		private static readonly string CmdLogDirectory = Environment.ExpandEnvironmentVariables("%appdata%\\YArchitech\\BIMSpace\\log\\CmdHistory");
	}
}
